package com.ohs.fo.action;

import java.io.File;
import java.text.ParseException;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.apache.commons.io.FileUtils;
import org.apache.struts2.ServletActionContext;

import com.ohs.bll.service.AccountService;
import com.ohs.bll.service.BookingService;
import com.ohs.bll.service.ExportService;
import com.ohs.bll.service.LocationService;
import com.ohs.bll.service.RoomService;
import com.ohs.bll.service.ScheduleService;
import com.ohs.bll.util.CommonUtil;
import com.ohs.bll.util.ConfigurationManager;
import com.ohs.bll.util.Constant;
import com.ohs.bll.util.DateUtil;
import com.ohs.bll.util.PasswordUtil;
import com.ohs.bo.form.LoginUser;
import com.ohs.dal.model.Account;
import com.ohs.dal.model.Booking;
import com.ohs.dal.model.Location;
import com.ohs.dal.model.Province;
import com.ohs.dal.model.Room;
import com.ohs.dal.model.Specialty;

public class UserAction extends AbstractAction {

	private AccountService accountService;
	private LocationService locationService;
	private BookingService bookingService;
	private RoomService roomService;
	private ScheduleService scheduleService;
	private ExportService exportService;
	private String username;
	private String password;
	private String oldpassword;
	private String name;
	private String locationName;
	private String age;
	private String phone;
	private String address;
	private String email;
	private String captcha;
	private String info;
	private String profilePath;
	private String longitude;
	private String latitude;
	private File image;
	private String imageContentType;
    private String imageFileName;
	private Integer numberOfBooking;
	private List<Booking> bookings;
	private List<Room> rooms;
	private String selectedRoom;
	private String selectedDate;
	private static String isSetupRoom;
	private static String isSetupSchedule;
	private List<Province> provinces;
	private String province;
	private List<Specialty> specialties;
	private String specialty1;
	private String specialty2;
	private String specialty3;
	private String specialty4;
	private String specialty5;

	public String register() throws Exception {
		// hack for auto disconnect from db issue
		try {
			accountService.getAllSpecialty();
		} catch (Exception e) {
			log.error("CAN'T CONNECT DB");
		}
		return "success";
	}

	public String registerSubmit() throws Exception {
		clearMessages();
		if (CommonUtil.checkCaptcha(ServletActionContext.getRequest().getSession(), captcha)) {
			Account account = new Account(username, PasswordUtil.encrypt(password), name, new Date());
			try {
				int realage = Integer.valueOf(age);
				account.setAge(realage);
			} catch (NumberFormatException ne) {
				
			}
			account.setEmail(email);
			account.setStep(Constant.STEP_REGISTERED_0);
			if (accountService.createDoctor(account, address, locationName, Long.parseLong(province))) {
				LoginUser loginUser = new LoginUser(account.getUsername(), Constant.STEP_REGISTERED_0);
				HttpServletRequest request = ServletActionContext.getRequest();
				request.getSession().setAttribute(Constant.USER_ACCOUNT, loginUser);
				request.getSession().setAttribute(Constant.USER_NAME, username);
				return "success";
			} else {				
				addActionMessage("Tên đăng nhập đã tồn tại");
			}
		} else {
			addActionMessage("Mã kí tự không đúng");
		}
		return "input";
	}

	public String login() throws Exception {
		// hack for auto disconnect from db issue
		try {
			accountService.getAllSpecialty();
		} catch (Exception e) {
			log.error("CAN'T CONNECT DB");
		}
		return "success";
	}
	
	public String forgotPass() throws Exception {
		return "success";
	}
	
	public String forgotPassSubmit() throws Exception {
		clearErrorsAndMessages();
		if (!accountService.forgotPass(username)) {
			addActionMessage("Tên đăng nhập hoặc email không có trong hệ thống");
			return "input";
		}
		return "success";
	}
	
	public String loginSubmit() throws Exception {
		clearMessages();
		LoginUser loginUser = accountService.checkLogin(username, password);
		if (loginUser != null) {
			HttpServletRequest request = ServletActionContext.getRequest();
			request.getSession().setAttribute(Constant.USER_ACCOUNT, loginUser);
			request.getSession().setAttribute(Constant.USER_NAME, username);
			if (loginUser.getStep() == Constant.STEP_REGISTERED_0) {
				return "step1";
			} else {
				return "success";
			}
		} else {
			addActionMessage("Tên đăng nhập hoặc mật khẩu không đúng.");
			return "input";
		}
	}
	
	public String logout() throws Exception {
		HttpServletRequest request = ServletActionContext.getRequest();
		request.getSession().removeAttribute(Constant.USER_ACCOUNT);
		request.getSession().removeAttribute(Constant.USER_NAME);
		return "success";
	}
	
	public String loadProfile() throws Exception {
		loadBookings();
		return "success";
	}

	private long loadBookings() throws ParseException {
		HttpServletRequest request = ServletActionContext.getRequest();
		rooms = roomService.findByAccount(CommonUtil.getUsername(request));
		long roomId = 0;
		if (rooms != null && rooms.size() > 0) {
			roomId = (selectedRoom != null && !"".equals(selectedRoom)) ? Long.parseLong(selectedRoom) : rooms.get(0).getRoomId();
			Date date = (selectedDate != null) ? DateUtil.stringToDate(selectedDate) : new Date();
			bookings = bookingService.findByRoomAndDate(roomId, date);
			numberOfBooking = bookings.size();
		}
		return roomId;
	}
	
	public String exportFile() throws Exception {
		long roomId = loadBookings();
		if (bookings != null && bookings.size() > 0) {
			String roomName = "";
			if (roomId > 0) {
				roomName = roomService.get(roomId).getName();
			}
			exportService.export(ServletActionContext.getResponse(), bookings, selectedDate, roomName);
		}
		return null;
	}
	
	public String updateProfile() throws Exception {
		clearErrorsAndMessages();
		HttpServletRequest request = ServletActionContext.getRequest();
		String user = (String) request.getSession().getAttribute(Constant.USER_NAME);
		Account account = accountService.get(user);
		name = account.getName();
		email = account.getEmail();
		age = account.getAge().toString();
		
		Location location = locationService.getByAccount(user);
		specialty1 = (location.getSpecialty1() != null) ? location.getSpecialty1().getSpecialtyId() + "" : "-1";
		specialty2 = (location.getSpecialty2() != null) ? location.getSpecialty2().getSpecialtyId() + "" : "-1";
		specialty3 = (location.getSpecialty3() != null) ? location.getSpecialty3().getSpecialtyId() + "" : "-1";
		specialty4 = (location.getSpecialty4() != null) ? location.getSpecialty4().getSpecialtyId() + "" : "-1";
		specialty5 = (location.getSpecialty5() != null) ? location.getSpecialty5().getSpecialtyId() + "" : "-1";
		latitude = location.getLatitudes();
		longitude = location.getLongitudes();
		
		address = location.getAddress();
		locationName = location.getName();
		info = location.getInfo();
		imageFileName = location.getImageUrl();
		
		province = location.getProvince().getProvinceId() + "";
		return "success";
	}
	
	public String submitProfile() throws Exception {
		clearMessages();
		
		HttpServletRequest request = ServletActionContext.getRequest();
		String user = (String) request.getSession().getAttribute(Constant.USER_NAME);
		
		Location location = locationService.getByAccount(user);
		String fileName = location.getImageUrl();
		if (imageFileName != null && !"".equals(imageFileName)) {
			String filePath = ConfigurationManager.getAsString(ConfigurationManager.CONFIG, "fileupload.path");
			fileName = generateFileName(imageFileName);
	        File fileToCreate = new File(filePath, fileName);
	        FileUtils.copyFile(image, fileToCreate);
	        imageFileName = fileName;
		}
        
		Account account = accountService.get(user);
		account.setName(name);
		account.setEmail(email);
		account.setAge(Integer.parseInt(age));
		long[] specialtyArr = new long[5];
		specialtyArr[0] = (!"".equals(specialty1) && specialty1 != null) ? Long.parseLong(specialty1) : -1;
		specialtyArr[1] = (!"".equals(specialty2) && specialty2 != null) ? Long.parseLong(specialty2) : -1;
		specialtyArr[2] = (!"".equals(specialty3) && specialty3 != null) ? Long.parseLong(specialty3) : -1;
		specialtyArr[3] = (!"".equals(specialty4) && specialty4 != null) ? Long.parseLong(specialty4) : -1;
		specialtyArr[4] = (!"".equals(specialty5) && specialty5 != null) ? Long.parseLong(specialty5) : -1;
		accountService.updateDoctor(account, new Location(locationName, info, address, fileName, latitude, longitude), Long.parseLong(province), specialtyArr);
        
		addActionMessage("Cập nhật thành công");
		return "success";
	}
	
	public String changepass() throws Exception {
		clearErrorsAndMessages();
		return "success";
	}
	
	public String changepassSubmit() throws Exception {
		clearMessages();
		HttpServletRequest request = ServletActionContext.getRequest();
		String user = (String) request.getSession().getAttribute(Constant.USER_NAME);
		
		Account account = accountService.get(user);
		if (account.getPassword().equals(PasswordUtil.encrypt(oldpassword))) {
			account.setPassword(PasswordUtil.encrypt(password));
			accountService.update(account);
			clearMessages();
			addActionMessage("Thay đổi mật khẩu thành công");
			return "success";
		} else {
			addActionMessage("Mật khẩu cũ không đúng");
			return "input";
		}
		
	}
	
	private String generateFileName(String fileName) {
		long time = Calendar.getInstance().getTimeInMillis();
		return time + "_" + fileName;
	}
	
	public String loadHelp() throws Exception {
		HttpServletRequest request = ServletActionContext.getRequest();
		profilePath = ConfigurationManager.getAsString(ConfigurationManager.CONFIG, "sitedomain") + "/" + 
					(String) request.getSession().getAttribute(Constant.USER_NAME);
		return "success";
	}
	
	public String poster() throws Exception {
		HttpServletRequest request = ServletActionContext.getRequest();
		profilePath = ConfigurationManager.getAsString(ConfigurationManager.CONFIG, "sitedomain") + "/" + 
					(String) request.getSession().getAttribute(Constant.USER_NAME);
		return "success";
	}
	
	public String loadYoursite() throws Exception {
		HttpServletRequest request = ServletActionContext.getRequest();
		profilePath = ConfigurationManager.getAsString(ConfigurationManager.CONFIG, "sitedomain") + "/include/" + 
				(String) request.getSession().getAttribute(Constant.USER_NAME);
		return "success";
	}
	
	public String getOldpassword() {
		return oldpassword;
	}

	public String getInfo() {
		return info;
	}

	public void setInfo(String info) {
		this.info = info;
	}

	public String getLongitude() {
		return longitude;
	}

	public void setLongitude(String longitude) {
		this.longitude = longitude;
	}

	public String getLatitude() {
		return latitude;
	}

	public void setLatitude(String latitude) {
		this.latitude = latitude;
	}

	public File getImage() {
		return image;
	}

	public void setImage(File image) {
		this.image = image;
	}

	public String getImageContentType() {
		return imageContentType;
	}

	public String getProvince() {
		return province;
	}

	public void setProvince(String province) {
		this.province = province;
	}

	public void setImageContentType(String imageContentType) {
		this.imageContentType = imageContentType;
	}

	public String getImageFileName() {
		return imageFileName;
	}

	public List<Province> getProvinces() {
		return locationService.getAllProvince();
	}

	public void setProvinces(List<Province> provinces) {
		this.provinces = provinces;
	}

	public void setImageFileName(String imageFileName) {
		this.imageFileName = imageFileName;
	}

	public void setOldpassword(String oldpassword) {
		this.oldpassword = oldpassword;
	}

	public LocationService getLocationService() {
		return locationService;
	}

	public ExportService getExportService() {
		return exportService;
	}

	public void setExportService(ExportService exportService) {
		this.exportService = exportService;
	}

	public void setLocationService(LocationService locationService) {
		this.locationService = locationService;
	}

	public String getUsername() {
		return username;
	}

	public String getProfilePath() {
		return profilePath;
	}

	public void setProfilePath(String profilePath) {
		this.profilePath = profilePath;
	}

	public void setUsername(String username) {
		this.username = username;
	}

	public List<Room> getRooms() {
		return rooms;
	}

	public void setRooms(List<Room> rooms) {
		this.rooms = rooms;
	}

	public String getPassword() {
		return password;
	}

	public AccountService getAccountService() {
		return accountService;
	}

	public void setAccountService(AccountService accountService) {
		this.accountService = accountService;
	}

	public void setPassword(String password) {
		this.password = password;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getAge() {
		return age;
	}

	public void setAge(String age) {
		this.age = age;
	}

	public String getPhone() {
		return phone;
	}

	public String getLocationName() {
		return locationName;
	}

	public void setLocationName(String locationName) {
		this.locationName = locationName;
	}

	public String getEmail() {
		return email;
	}

	public void setEmail(String email) {
		this.email = email;
	}

	public void setPhone(String phone) {
		this.phone = phone;
	}

	public String getAddress() {
		return address;
	}

	public List<Booking> getBookings() {
		return bookings;
	}

	public void setBookings(List<Booking> bookings) {
		this.bookings = bookings;
	}

	public void setAddress(String address) {
		this.address = address;
	}

	public String getCaptcha() {
		return captcha;
	}

	public void setCaptcha(String captcha) {
		this.captcha = captcha;
	}

	public BookingService getBookingService() {
		return bookingService;
	}

	public void setBookingService(BookingService bookingService) {
		this.bookingService = bookingService;
	}

	public RoomService getRoomService() {
		return roomService;
	}

	public void setRoomService(RoomService roomService) {
		this.roomService = roomService;
	}

	public ScheduleService getScheduleService() {
		return scheduleService;
	}

	public void setScheduleService(ScheduleService scheduleService) {
		this.scheduleService = scheduleService;
	}

	public Integer getNumberOfBooking() {
		return numberOfBooking;
	}

	public void setNumberOfBooking(Integer numberOfBooking) {
		this.numberOfBooking = numberOfBooking;
	}

	public String getIsSetupRoom() {
		if(isSetupRoom == null) {
			HttpServletRequest request = ServletActionContext.getRequest();
			isSetupRoom = String.valueOf(roomService.isSetupRoom(CommonUtil.getUsername(request)));
		}
		return isSetupRoom;
	}

	public void setIsSetupRoom(String isSetupRoom) {
		UserAction.isSetupRoom = isSetupRoom;
	}

	public String getIsSetupSchedule() {
		if (isSetupSchedule == null) {
			HttpServletRequest request = ServletActionContext.getRequest();
			isSetupSchedule = String.valueOf(scheduleService.isSetupSchedule(CommonUtil.getUsername(request)));
		}
		return isSetupSchedule;
	}

	public void setIsSetupSchedule(String isSetupSchedule) {
		UserAction.isSetupSchedule = isSetupSchedule;
	}

	public String getSelectedRoom() {
		return selectedRoom;
	}

	public void setSelectedRoom(String selectedRoom) {
		this.selectedRoom = selectedRoom;
	}

	public String getSelectedDate() {
		return selectedDate;
	}

	public void setSelectedDate(String selectedDate) {
		this.selectedDate = selectedDate;
	}

	public List<Specialty> getSpecialties() {
		return accountService.getAllSpecialty();
	}

	public void setSpecialties(List<Specialty> specialties) {
		this.specialties = specialties;
	}

	public String getSpecialty1() {
		return specialty1;
	}

	public void setSpecialty1(String specialty1) {
		this.specialty1 = specialty1;
	}

	public String getSpecialty2() {
		return specialty2;
	}

	public void setSpecialty2(String specialty2) {
		this.specialty2 = specialty2;
	}

	public String getSpecialty3() {
		return specialty3;
	}

	public void setSpecialty3(String specialty3) {
		this.specialty3 = specialty3;
	}

	public String getSpecialty4() {
		return specialty4;
	}

	public void setSpecialty4(String specialty4) {
		this.specialty4 = specialty4;
	}

	public String getSpecialty5() {
		return specialty5;
	}

	public void setSpecialty5(String specialty5) {
		this.specialty5 = specialty5;
	}

}